﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using WeifenLuo.WinFormsUI.Docking;
using Arles.src.view.controls;
using Arles.src.utils;
using Microsoft.Xna.Framework.Graphics;
using Arles.src.controller.Commands;
using ArlesInterfaces.Editor;
using ArlesInterfaces.Render;
using System.IO;
using Arles.src.controller;
using Arles.src.model;

namespace Arles.src.view
{
    public partial class FMainForm : Form, IMainForm
    {
        //Private members
        FScene sceneWindow;
        FOutput outputWindow;
        FHistory historyWindow;
        FProperties propertiesWindow;
        Canvas canvas;

        //Public members
        

        #region Properties
        public Control Canvas
        {
            get { return canvas; }
        }

        public IOutput Output
        {
            get { return outputWindow; }
        }

        public PropertyGrid Properties
        {
            get { return propertiesWindow.Grid; }
        }

        public TreeView SceneTree
        {
            get { return sceneWindow.SceneTree; }
        }

        #endregion

        #region Initialize
        public FMainForm()
        {
            InitializeComponent();
            canvas = new Canvas();
            outputWindow = new FOutput();
            outputWindow.HideOnClose = true;
            historyWindow = new FHistory();
            historyWindow.HideOnClose = true;
            propertiesWindow = new FProperties();
            propertiesWindow.HideOnClose = true;
            sceneWindow = new FScene();
            sceneWindow.HideOnClose = true;
        }

        private void MainForm_Load(object sender, EventArgs e)
        {
            #region DockPanels
            dockPanel.ActiveAutoHideContent = null;
            dockPanel.Parent = this;

       
            string configFile = Path.Combine(Path.GetDirectoryName(Application.ExecutablePath), "DockPanel.config");

            if (File.Exists(configFile) && ConfigFile.Instance.Attributes.SaveLayout)
                dockPanel.LoadFromXml(configFile, new DeserializeDockContent(GetContentFromPersistString));
            else
                CreateBasicLayout();

            dockPanel.DocumentStyle = DocumentStyle.DockingSdi;

            #endregion

            Editor.Instance.Initialize(historyWindow);
        }

        private void CreateBasicLayout()
        {
            propertiesWindow.Show(dockPanel, DockState.DockRight);
            sceneWindow.Show(dockPanel, DockState.DockRight);
            outputWindow.Show(dockPanel, DockState.DockBottomAutoHide);
            historyWindow.Show(dockPanel, DockState.DockBottomAutoHide);
            canvas.Show(dockPanel, DockState.Document);
        }

        private IDockContent GetContentFromPersistString(string persistString)
        {
            if (persistString == typeof(FProperties).ToString())
                return propertiesWindow;
            else if (persistString == typeof(FScene).ToString())
                return sceneWindow;
            else if (persistString == typeof(FOutput).ToString())
                return outputWindow;
            else if (persistString == typeof(FHistory).ToString())
                return historyWindow;
            else
                return canvas;
        }
        #endregion

        #region MenuStrip

        #region File Menu
        private void openToolStripMenuItem_Click(object sender, EventArgs e)
        {
            OpenFileDialog openFile = new OpenFileDialog();

            openFile.InitialDirectory = Application.ExecutablePath;
            openFile.Filter = "Terrain files (*.terrain)|*.terrain |All files (*.*)|*.*";
            openFile.FilterIndex = 1;
            openFile.RestoreDirectory = true;

            if (openFile.ShowDialog() == DialogResult.OK)
            {
            }
        }

        private void exitToolStripMenuItem_Click(object sender, EventArgs e)
        {
            Application.Exit();
        }

        #endregion

        #region Edit Menu
        private void undoToolStripMenuItem_Click(object sender, EventArgs e)
        {
            Editor.Instance.Invoker.Undo();
        }

        private void redoToolStripMenuItem_Click(object sender, EventArgs e)
        {
            Editor.Instance.Invoker.Redo();
        }

        #endregion

        #region View Menu
        private void toolBarToolStripMenuItem_Click(object sender, EventArgs e)
        {
            toolStrip.Visible = toolBarToolStripMenuItem.Checked = !toolBarToolStripMenuItem.Checked;
        }

        private void statusBarToolStripMenuItem_Click(object sender, EventArgs e)
        {
            statusStrip.Visible = statusBarToolStripMenuItem.Checked = !statusBarToolStripMenuItem.Checked;
        }

        private void sceneToolStripMenuItem_Click(object sender, EventArgs e)
        {
            SceneShow();
        }

        public void SceneShow()
        {
            sceneWindow.Show(dockPanel);
        }

        private void terrainToolStripMenuItem_Click(object sender, EventArgs e)
        {
            PropertyShow();
        }

        public void PropertyShow()
        {
            propertiesWindow.Show(dockPanel);
        }

        private void outputToolStripMenuItem_Click(object sender, EventArgs e)
        {
            OutputShow();
        }

        public void OutputShow()
        {
            outputWindow.Show(dockPanel);
        }

        private void historyToolStripMenuItem_Click(object sender, EventArgs e)
        {
            HistoryShow();
        }

        public void HistoryShow()
        {
            historyWindow.Show(dockPanel);
        }

        #endregion

        #region Terrain Menu

        #endregion

        #region Render Menu
        private void solidToolStripMenuItem_Click(object sender, EventArgs e)
        {
            FillModeCommand fillModeCommand = new FillModeCommand(Editor.Instance.Render, FillMode.Solid);
            Editor.Instance.Invoker.ExecuteCommand(fillModeCommand);
        }

        private void wireframeToolStripMenuItem_Click(object sender, EventArgs e)
        {
            FillModeCommand fillModeCommand = new FillModeCommand(Editor.Instance.Render, FillMode.WireFrame);
            Editor.Instance.Invoker.ExecuteCommand(fillModeCommand);
        }

        private void noneToolStripMenuItem_Click(object sender, EventArgs e)
        {
            MultiSampleTypeCommand sampletypeCommand = new MultiSampleTypeCommand(Editor.Instance.Render, 
                MultiSampleType.None);
            Editor.Instance.Invoker.ExecuteCommand(sampletypeCommand);
        }

        private void twoxToolStripMenuItem_Click(object sender, EventArgs e)
        {
            MultiSampleTypeCommand sampletypeCommand = new MultiSampleTypeCommand(Editor.Instance.Render,
                MultiSampleType.TwoSamples);
            Editor.Instance.Invoker.ExecuteCommand(sampletypeCommand);
        }

        private void fourxToolStripMenuItem_Click(object sender, EventArgs e)
        {
            MultiSampleTypeCommand sampletypeCommand = new MultiSampleTypeCommand(Editor.Instance.Render,
                MultiSampleType.FourSamples);
            Editor.Instance.Invoker.ExecuteCommand(sampletypeCommand);
        }

        private void showStatsToolStripMenuItem_Click(object sender, EventArgs e)
        {
            ShowStatsCommand statsCommand = new ShowStatsCommand(Editor.Instance.Render, true);
            Editor.Instance.Invoker.ExecuteCommand(statsCommand);
        }

        private void hideStatsToolStripMenuItem_Click(object sender, EventArgs e)
        {
            ShowStatsCommand statsCommand = new ShowStatsCommand(Editor.Instance.Render, false);
            Editor.Instance.Invoker.ExecuteCommand(statsCommand);
        }

        private void fixedTimeStepToolStripMenuItem_Click(object sender, EventArgs e)
        {
            TimeStepModeCommand stepCommand = new TimeStepModeCommand(Editor.Instance.Render,
                true);
            Editor.Instance.Invoker.ExecuteCommand(stepCommand);
        }

        private void unfixedTimeStepToolStripMenuItem_Click(object sender, EventArgs e)
        {
            TimeStepModeCommand stepCommand = new TimeStepModeCommand(Editor.Instance.Render,
                false);
            Editor.Instance.Invoker.ExecuteCommand(stepCommand);
        }


        private void resetStatsToolStripMenuItem_Click(object sender, EventArgs e)
        {
            Editor.Instance.Render.ResetStats();
        }
        #endregion

        #region Help Menu
        private void contentsToolStripMenuItem_Click(object sender, EventArgs e)
        {
            try
            {
                System.Diagnostics.Process.Start(Application.StartupPath + "\\resources\\help\\Index.html");
            }
            catch (Exception)
            {
                LogFactory.Instance.Write("Error a la hora de cargar el fichero de ayuda");
            }
        }

        private void aboutArlesEditorToolStripMenuItem_Click(object sender, EventArgs e)
        {
            MessageBox.Show("Powered by XNACommunity\n\n" +
                            "Alejandro Urbano - goefuika@gmail.com\n" +
                            "Javier Cantón Ferrero - javiuniversidad@gmail.com\n" +
                            "Ruben Lopez - rlopezll@gmail.com", "Authors");
        }

        #endregion

        #region Mouse Event

        private void toolStrip_MouseDown(object sender, MouseEventArgs e)
        {
            this.toolStrip.Focus();
        }

        private void menuStrip_MouseDown(object sender, MouseEventArgs e)
        {
            this.menuStrip.Focus();
        }

        private void statusStrip_MouseDown(object sender, MouseEventArgs e)
        {
            this.statusStrip.Focus();
        }

        private void editToolStripMenuItem_MouseDown(object sender, MouseEventArgs e)
        {
            this.menuStrip.Focus();
        }

        private void fileToolStripMenuItem_MouseDown(object sender, MouseEventArgs e)
        {
            this.menuStrip.Focus();
        }

        private void viewToolStripMenuItem_MouseDown(object sender, MouseEventArgs e)
        {
            this.menuStrip.Focus();
        }

        private void terrainToolStripMenuItem1_MouseDown(object sender, MouseEventArgs e)
        {
            this.menuStrip.Focus();
        }

        private void renderToolStripMenuItem_MouseDown(object sender, MouseEventArgs e)
        {
            this.menuStrip.Focus();
        }

        private void helpToolStripMenuItem_MouseDown(object sender, MouseEventArgs e)
        {
            this.menuStrip.Focus();
        }

        private void MainForm_KeyDown(object sender, KeyEventArgs e)
        {
            /* Doesn't work */
            if (e.Control && e.KeyCode.ToString() == "Z")
                Editor.Instance.Invoker.Undo();
            if (e.Control && e.KeyCode.ToString() == "Y")
                Editor.Instance.Invoker.Redo();
        }

        #endregion

        #endregion

        #region ToolBar
        private void toolStripButton1_Click(object sender, EventArgs e)
        {

        }

        private void toolStripButton2_Click(object sender, EventArgs e)
        {

        }

        private void toolStripButton3_Click(object sender, EventArgs e)
        {

        }

        #endregion

        #region Exit
        private void MainForm_FormClosing(object sender, FormClosingEventArgs e)
        {
            string configFile = Path.Combine(Path.GetDirectoryName(Application.ExecutablePath), "DockPanel.config");
            if (ConfigFile.Instance.Attributes.SaveLayout)
                dockPanel.SaveAsXml(configFile);
            else if (File.Exists(configFile))
                File.Delete(configFile);
        }

        #endregion

    }
}
